package com.util;

import java.awt.image.BufferedImage;
import java.util.HashMap;

public class Workspace {
	private Design workingDesign;
	private HashMap<String, Design> designs;
	private StorageManager manager;

	public Workspace(String username, String password) {
		// establish database connection
		manager = new MySQLManager(MySQLManager.CONNECTOR + Constant.HOST
				+ Constant.DB, username, password);

		if (isConnected()) {
			designs = new HashMap<String, Design>();
			manager.populateDesigns(designs);
		} else
			designs = null;
	}

	/**
	 * Adds a Shelf to the storage medium and to the working design
	 * 
	 * @param x
	 *            - Coordinate
	 * @param y
	 *            - Coordinate
	 * @param begId
	 *            - Beginning Id of Shelf
	 * @param endId
	 *            - Ending Id of Shelf
	 * @return true for success, false for failure
	 */
	public boolean addShelf(Shelf s) {
		if (workingDesign != null) {
			if (manager.addShelf(s, workingDesign.getName())) {
				workingDesign.lib.addShelf(s);
				return true;
			}
			return false;
		}
		return false;

	}

	/**
	 * Creates a Design with a name and an image. Doesn't allow duplicate names
	 * for arbitrary user
	 * 
	 * @param name
	 *            - Name of library
	 * @param img
	 *            - image of library
	 * @return true for success, false for failure
	 */
	public boolean createDesign(String name, BufferedImage img) {
		// if name is already in use
		if (!designs.containsKey(name)) {
			Design d = new Design(name, img);
			// add to local copy
			designs.put(d.getName(), d);
			// add to storage

			return manager.insertDesign(d);
		}
		return false;
	}

	/**
	 * Delete an existing library design from storage medium and local list of
	 * designs
	 * 
	 * @param name
	 *            - Name of library design to remove
	 * @return true for success, false for failure
	 */
	public boolean deleteDesign(String name) {
		if (designs.containsKey(name) && manager.deleteDesign(name)) {
			designs.remove(name);
			return true;
		}
		return false;
	}

	/**
	 * Gets list of user's designs
	 * 
	 * @return list of designs
	 */
	public HashMap<String, Design> getDesigns() {
		return designs;
	}

	/**
	 * Gets the current working design
	 * 
	 * @return working design
	 */
	public Design getWorkingDesign() {
		return workingDesign;
	}

	/**
	 * Checks if the Storage Manager is connected
	 * 
	 * @return state of storage connection
	 */
	public boolean isConnected() {
		return manager.isConnected();
	}

	/**
	 * Removes existing shelf from the storage medium and the working design
	 * 
	 * @param pos
	 *            - Location of shelf in to be removed
	 * @return true for success, false for failure
	 */
	public boolean removeShelf(int pos) {
		if (workingDesign != null) {
			Shelf s = workingDesign.lib.getShelves().get(pos);
			if (manager
					.removeShelf(s.getX(), s.getY(), workingDesign.getName())) {
				workingDesign.lib.removeShelf(pos);
				return true;
			} else {
				return false;
			}
		} else {
			return false;
		}
	}

	/**
	 * Removes working design
	 * 
	 * @return true for success, false for failure
	 */
	public boolean removeWorkingDesign() {
		if (workingDesign != null) {
			// update storage
			manager.updateDesign(workingDesign);
			// update local copy
			designs.put(workingDesign.getName(), workingDesign);
			workingDesign = null;
			return true;
		}
		return false;
	}

	/**
	 * Sets the working design in the workspace
	 * 
	 * @param name
	 *            - Name of library design to set as working design
	 * @return true for success, false for failure
	 */
	public boolean setWorkingDesign(String name) {
		if (designs.containsKey(name) && workingDesign == null) {
			workingDesign = designs.get(name);
			return true;
		}
		return false;
	}

	/**
	 * Update the beginning and ending id of a selected shelf
	 * 
	 * @param pos
	 *            - Location of the selected shelf
	 * @param beg
	 *            - Beginning id of shelf
	 * @param end
	 *            - Ending id of shelf
	 */
	public boolean updateShelf(int pos, Shelf s) {
		if (workingDesign != null) {
			if (manager.updateShelf(s)) {
				workingDesign.lib.updateShelf(pos, s);
				return true;
			}
		}
		return false;
	}
}
